extends CanvasLayer
class_name MapView



signal close
signal select_entity(data)


var mode = 2

# 选择实体模式，将可以触发剧情触发器信号
var select_entity_mode = false

const MOVE_MODE = 2
const SELECT_MODE = 1

const SoilTree = preload("res://tool/page/map/mapView/component/SoilTree.tscn")
const MapDoor = preload("res://tool/page/map/mapView/component/MapDoor.tscn")
const MapInteractive = preload("res://tool/page/map/mapView/component/MapInteractive.tscn")
const MapProp = preload("res://tool/page/map/mapView/component/MapProp.tscn")
const MapCenterRecover = preload("res://tool/page/map/mapView/component/MapCenterRecover.tscn")
const MapDecoration = preload("res://tool/page/map/mapView/component/MapDecoration.tscn")
const MapNpc = preload("res://tool/page/map/mapView/component/MapNpc.tscn")
const AudioControlNode = preload("res://tool/page/map/mapView/audioArea/AudioControlNode.tscn")
const SpriteAreaCell = preload("res://tool/page/map/mapView/spriteArea/SpriteAreaCell.tscn")

onready var map_layer = $mapLayer
onready var mode_op = $uiLayer/HBoxContainer/OptionButton
onready var move_layer = $uiLayer/moveLayer
onready var select_layer = $mapLayer/SelectLayer
onready var entity_layer = $mapLayer/EntityLayer
onready var select_box = $mapLayer/SelectLayer/SelectBox
onready var select_right_menu = $uiLayer/SelectRightMenu
onready var show_entity_menu = $uiLayer/showEntity
onready var audio_layer = $mapLayer/audioLayer
onready var sprite_layer = $mapLayer/spriteLayer

onready var map_bottom = $uiLayer/MapViewBottom


#var copy_data = {
#	"type": 1,
#	"data":{
#
#	}
#}


# 待copy的数据
var copy_data = null


var map_register

var map_instance = null


func _ready():
	update_mode()
	
	select_right_menu.visible = false
	show_entity_menu.visible = false
	
	# 注册到ui里供其它组件调用
	MainTool.getUILayer().register_ui("MapView", self)
	


	

func set_data(map_register):
	self.map_register = map_register
	
	for child in $mapLayer/mapBox.get_children():
		child.queue_free()
		
	map_instance = load(map_register["path"]).instance()
	$mapLayer/mapBox.add_child(map_instance)
	
	
	entity_update()
	map_bottom.set_map_name(map_register["name"])


func entity_update():
	for child in entity_layer.get_children():
		child.queue_free()
	
	
	if $uiLayer/showEntity/PanelContainer/VBoxContainer/soilTree.pressed:
		# 土壤
		var tree_list = DataSource.get_data_by_list(DataSource.map_trees, map_register["id"], "mapId")
		
		for tree in tree_list:
			var tree_ui = SoilTree.instance()
			entity_layer.add_child(tree_ui)
			tree_ui.set_data(tree)
	
	if $uiLayer/showEntity/PanelContainer/VBoxContainer/door.pressed:
		# 传送门
		var door_list = DataSource.get_data_by_list(DataSource.map_door, map_register["id"], "mapId")

		for door in door_list:
			var ui = MapDoor.instance()
			entity_layer.add_child(ui)
			ui.set_data(door)
	
	if $uiLayer/showEntity/PanelContainer/VBoxContainer/interactive.pressed:
		# 障碍物
		var interactive_list = DataSource.get_data_by_list(DataSource.map_interactive, map_register["id"], "mapId")

		for interactive in interactive_list:
			var ui = MapInteractive.instance()
			entity_layer.add_child(ui)
			ui.set_data(interactive)
	
	if $uiLayer/showEntity/PanelContainer/VBoxContainer/prop.pressed:
		# 道具
		var prop_list = DataSource.get_data_by_list(DataSource.map_prop, map_register["id"], "mapId")
		for prop in prop_list:
			var ui = MapProp.instance()
			entity_layer.add_child(ui)
			ui.set_data(prop)
	
	if $uiLayer/showEntity/PanelContainer/VBoxContainer/centerRecover.pressed:
		# 恢复中心
		var center_list = DataSource.get_data_by_list(DataSource.map_center_recover, map_register["id"], "mapId")
		for center in center_list:
			var ui = MapCenterRecover.instance()
			entity_layer.add_child(ui)
			ui.set_data(center)
	
	if $uiLayer/showEntity/PanelContainer/VBoxContainer/npc.pressed:
		# npc
		var npc_list = DataSource.get_data_by_list(DataSource.map_npc, map_register["id"], "mapId")
		for npc in npc_list:
			var ui = MapNpc.instance()
			entity_layer.add_child(ui)
			ui.set_data(npc)
	
	if $uiLayer/showEntity/PanelContainer/VBoxContainer/decoration.pressed:
		# 装饰品
		var decoration_list = DataSource.get_data_by_list(DataSource.map_decoration, map_register["id"], "mapId")
		for decoration in decoration_list:
			var ui = MapDecoration.instance()
			entity_layer.add_child(ui)
			ui.set_data(decoration)

var drag = false  
var drag_start_mouse_pos = Vector2()  
var drag_start_offset = Vector2() 

var scale_falg = false

var start_scale = 1

var zoom_speed = 0.1  # 缩放速度，可以根据需要调整  
var min_zoom = 0.1    # 最小缩放级别  
var max_zoom = 10.0    # 最大缩放级别  





func update_mode():
	mode = mode_op.get_selected_id()
	# 避免影响选择层
	move_layer.visible = mode == MOVE_MODE
	

func _on_OptionButton_item_selected(index):
	update_mode()


func set_map_scale(scale):
	var pre_scale = map_layer.scale.x
	
	map_layer.scale = Vector2(scale, scale)
	
	# 需要更新坐标位置，调整视图中心
	
	var new_offset = map_layer.offset * scale / pre_scale
	
	set_map_offset(new_offset)


func set_map_offset(offset):
	map_layer.offset = offset


func select_grid(x, y):
	select_box.rect_position.x = x+50000
	select_box.rect_position.y = y+50000
	
	map_bottom.update()
	
	
	set_map_offset(Vector2(x+600, -y+300))


func _on_moveLayer_gui_input(event):
	if event is InputEventMouseButton and mode == MOVE_MODE:  
		if event.button_index == BUTTON_LEFT and event.pressed:  
			drag = true  
			drag_start_mouse_pos = move_layer.get_global_mouse_position()  
			drag_start_offset = map_layer.offset  

		if event.button_index == BUTTON_LEFT and not event.pressed and drag:  
			drag = false  
		
		# 这里以鼠标滚轮为例来控制缩放，但你也可以使用其他输入方式  
		if event.button_index == BUTTON_WHEEL_UP:  
			var scale = map_layer.scale.x + zoom_speed
			scale = clamp(scale, min_zoom, max_zoom)
			set_map_scale(scale)	
			
		elif event.button_index == BUTTON_WHEEL_DOWN:  
			var scale = map_layer.scale.x - zoom_speed
			scale = clamp(scale, min_zoom, max_zoom)
			set_map_scale(scale)	
		
	if drag and mode == MOVE_MODE:  
		var delta = move_layer.get_global_mouse_position() - drag_start_mouse_pos 
		 # 更新相机的偏移量以平移视图
		set_map_offset(drag_start_offset + delta) 
		 


func _on_SelectLayer_gui_input(event):
	if event is InputEventMouseButton:  
		if event.button_index == BUTTON_LEFT and event.pressed:  
			# 鼠标左键被按下  
			var position = event.position
			
			var x = int(position.x)
			var y = int(position.y)
			
			x -= x % 16
			y -= y % 16
			# 使用click_position来调整UI元素的位置  
			select_box.rect_position = Vector2(x, y)
			
			map_bottom.update_data()
			
		
		

func _on_SelectBox_gui_input(event):
	if event is InputEventMouseButton:  
		if event.button_index == BUTTON_RIGHT and event.pressed:  
			# 鼠标右键键被按下 并且在当前选中格子
			select_right_menu.visible = true
			

# 获取当前选中的地图信息
func get_select_position_info():
	return {
		"x": select_box.rect_position.x - 50000,
		"y": select_box.rect_position.y - 50000,
		"map_register": map_register
	}




var audio_area_show = false

func _on_audioButton_button_up():
	audio_area_show = !audio_area_show
	map_area_update()

func map_area_update():
	for child in audio_layer.get_children():
		child.queue_free()
	
	if !audio_area_show:
		$uiLayer/HBoxContainer/audioButton.text = "显示音乐区域"
		# 关闭状态
		return
	else:
		$uiLayer/HBoxContainer/audioButton.text = "隐藏音乐区域"
	
	var audios = ModMapParseUtil.parse_audio(map_instance, {})
	
	for audio_area in audios:
		var polygon_2d = audio_area["child"][0]
		var polygon = polygon_2d["polygon"]
		var position = polygon_2d["position"]
		
		var music_area_id = audio_area["script_json"]["music_area_id"]
		
		# 添加控制节点
		
		var color = get_random_color()
		
		var audio_control_node = AudioControlNode.instance()
		audio_layer.add_child(audio_control_node)
		
		var center_vec = calculate_polygon_center(polygon)
		
		audio_control_node.set_position(Vector2(center_vec.x+50000+position[0], center_vec.y+50000+position[1]))
		
		audio_control_node.set_font_color(color)
		
		# 加入连线
		var line_2d = Line2D.new()
		line_2d.width = 2
		
		line_2d.default_color = color
	
		# 加入第一个点首尾相连
		polygon.append(polygon[0])
		
		for po in polygon:
			line_2d.add_point(Vector2(po[0]+50000+position[0], po[1]+50000+position[1]))
			
		audio_layer.add_child(line_2d)
		
		audio_control_node.set_line_2d(line_2d)
		audio_control_node.set_music_area_id(music_area_id)

func get_random_color():
	var r = randf()  
	var g = randf()  
	var b = randf()
	return Color(r, g, b)
# 计算多边形中心点
func calculate_polygon_center(vertices: Array) -> Vector2:  
	var total_x = 0.0  
	var total_y = 0.0  
	var num_vertices = vertices.size()  
	  
	for vertex in vertices:  
		total_x += vertex[0]  
		total_y += vertex[1]  
	  
	# 计算平均值  
	var center_x = total_x / num_vertices  
	var center_y = total_y / num_vertices  
	  
	return Vector2(center_x, center_y)


func sprite_area_update():
	
	for child in sprite_layer.get_children():
		
		child.visible = sprite_area_show
		
	
	if !sprite_area_show:
		# 关闭状态
		$uiLayer/HBoxContainer/spriteButton.text = "显示精灵分布"
		return	
	else:
		$uiLayer/HBoxContainer/spriteButton.text = "隐藏精灵分布"
	
	var top_json = {
		"resource":{},
		"map":{}
	}
	
	if sprite_layer.get_child_count() == 0:
		# 未初始化
		var sprite_areas = ModMapParseUtil.parse_entounter_poke(map_instance, top_json)
		
		for sprite_area in sprite_areas:
			var area = sprite_area["child"][0]
			var cells = area["cells"]
			
			var area_id = sprite_area["script_json"]["poke_id"]
			
			var color = get_random_color()
			
			for key in cells.keys():
				for cell in cells[key]:
					var sprite_area_cell = SpriteAreaCell.instance()
					sprite_layer.add_child(sprite_area_cell)
					
					var base_x = area["position"][0] + sprite_area["position"][0]
					var base_y = area["position"][1] + sprite_area["position"][1]
					
					sprite_area_cell.rect_position = Vector2(base_x+cell[0]*16+50000, base_y+cell[1]*16+50000)
				
					sprite_area_cell.set_area_id(area_id)
					sprite_area_cell.set_color(color)
			

var sprite_area_show = false


# 显示遇怪区域
func _on_spriteButton_button_up():
	sprite_area_show = !sprite_area_show
	
	sprite_area_update()


func _on_closeButton_button_up():
	emit_signal("close")
	MainTool.getUILayer().pop_ui()


func emit_select_signal(type, data):
	emit_signal("select_entity", {
		"type":type,
		"data":data,
		"map_register":map_register,
	})



func _on_entityButton_button_up():
	show_entity_menu.visible = true
	
func _on_showOkButton_button_up():
	show_entity_menu.visible = false
	entity_update()
